<?php

/**
 *Simple CRUD Code Generator
 *Email:  support@crazedcoders.com
 *Website: http://www.crazedcoders.com/
 *Copyright (C) 2007 CrazedCoders
 *
 *This program is free software: you can redistribute it and/or modify
 *it under the terms of the GNU General Public License as published by
 *the Free Software Foundation, either version 3 of the License, or
 *(at your option) any later version.
 *
 *THE PROGRAM IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 *IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 *FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 *AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 *LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 *OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 *SOFTWARE.
 *
 *You should have received a copy of the GNU General Public License
 *along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

// common functions

# function for getting foreign keys from a table
function getFKeys( $table ) {
	$fkeys = array();
	//for( $k = 0; $k < sizeof( $table ); $k++ ) {
	foreach( $table as $k=>$value ) {
		if( is_array($table[$k])
				&& array_key_exists( 2, $table[$k] )
				&& $table[$k][2]['constraint_type'] == 'FOREIGN KEY' ) {
			array_push( $fkeys, $table[$k][2] );
			//echo "fkeyname : ".toFKeyName( $table[$k][2]['column_name'] )."\n";
		}
	}
	return($fkeys);
}

# funciton for getting the primary key from a table
function getPKey( $table ) {
	//for( $k = 0; $k < sizeof( $table ); $k++ ) {
	foreach( $table as $k=>$value ) {
		if( ! is_int( $k ) ) {
			continue;
		}
		if( $table[$k][2]['constraint_type'] == 'PRIMARY KEY' ) {
			$assoc = $table[$k][2];
			$primaryKey = toCamelCaseMember($table[$k][2]['column_name']);
			//echo "k: $k\n";
			//echo "assoc: \n"; var_dump( $assoc );
			//echo "primaryKey: $primaryKey\n";
			return( $primaryKey );
		}
	}
	return "";
}


function findManyToManyForTable( $table ) {
	$manyTables = array();
	foreach( con::$manyToMany as $k=>$manyTable ) {
		if( ! is_int( $k ) )
			continue;
		if( $manyTable[0][2]['referenced_table_name'] ==
				$table[0][2]['table_name']
				|| $manyTable[1][2]['referenced_table_name'] ==
				$table[0][2]['table_name'] ) {
			array_push( $manyTables, $manyTable );
		}
	}
	return( $manyTables );
}

// stores the tables that are referenced in a
// many to many with $table
function findRefManyColumnsFromTable( $table ) {
	$tablename = toCamelCase( $table[0][2]['table_name'] );
	$manyTables = findManyToManyForTable( $table );
	$refManyColumns = array();	// stores the tables that are referenced in a
								// many to many with $table

	// find the names of the other table
	foreach( $manyTables as $k=>$manyTable ) {
		if( toCamelCase($manyTable[0][2]['referenced_table_name'])
				== $tablename ) {
			$elem = array();
			$elem['away_column'] = $manyTable[1];
			$elem['home_column'] = $manyTable[0];
			//array_push( $refManyColumns['away_column'], $manyTable[1] );
			array_push( $refManyColumns, $elem );
		}
		else {
			$elem = array();
			$elem['away_column'] = $manyTable[0];
			$elem['home_column'] = $manyTable[1];
			//array_push( $refManyColumns['away_column'], $manyTable[0] );
			array_push( $refManyColumns, $elem );
		}
	}
	return( $refManyColumns );
}
# convert to CamelCase function

function toCamelCase( $in ) {
	
	$ret = str_replace(' ','_',ucwords(preg_replace('/[^A-Z^a-z^0-9]+/',' ',$in)));
	if( $ret == "Default" ) {
		$ret = "DefaultOption";
	}
	return( $ret );
	
	//return $in;
}

function toCamelCaseMember( $in ) {
	
	$ret = ( strtolower( substr( $in, 0, 1 )) .
		substr( toCamelCase( $in ), 1, strlen( $in ) - 1 ) );
	if( $ret == "default" ) {
		$ret = "defaultOption";
	}
	return( $ret );
	
	//return $in;
}

function toFKeyName( $memberName ) {
	//echo "memberName : $memberName\n";
	//echo " substr( strtolower( $memberName ), sizeof( $memberName ) - 3,2):".
	// substr( strtolower( $memberName ), sizeof( $memberName ) - 3, 2 )."\n";
	$ret = null;
	if( substr( strtolower( $memberName ), sizeof( $memberName ) - 3, 2 )
			== 'id' ) {
		$ret = ( toCamelCaseMember( substr( $memberName,
						0, sizeof( $memberName ) - 3 ) ) );
	}
	if( $ret == "default" ) {
		$ret = "defaultOption";
	}
	return( $ret );
}



/**
 * pre: tablename corresponds to table with only 2 foreign keys and only 2
 * columns
 */
function addMappingTable( $table, $tablename ) {
	$table1 = $table[$tablename][0][2];
	$table2 = $table[$tablename][1][2];

	// fixme: add hibernate stuff here
}


#echo "var_dump( \$tables );";
#var_dump( $tables );


function getTableColumns( $tableName ) {
	$query = "SELECT data_type, column_name FROM Information_Schema.Columns WHERE ";
	$query .= " table_name = '". $tableName . "'";
	if( con::$dbtype == 'mysql' ) {
		$query.= "
					AND table_schema <> 'INFORMATION_SCHEMA'
					AND table_schema = '".con::$dbname."'; ";
	}
	else if ( con::$dbtype == 'mssql' ) {
		$query.= "
					AND table_schema <> 'INFORMATION_SCHEMA'
					AND table_catalog = '".con::$dbname."'; ";
	}
	if( con::$dbtype == 'mysql' ) {
		$rid = mysql_query( $query );
	}
	else if ( con::$dbtype == 'mssql' ) {
		$rid = mssql_query( $query );
	}
	$columns = array();
	while( $assoc = (con::$dbtype=='mysql')?mysql_fetch_assoc( $rid )
		:((con::$dbtype=='mssql')?mssql_fetch_assoc($rid)
		:array()) ) {
		$columns[toCamelCaseMember($assoc['column_name'])] =
			$assoc['data_type'];
		//$columns['\''.$assoc['column_name'].'\''] =
		//	$assoc['data_type'];
	}
	return( $columns );
}


/**
 * gets all combinations of items from an array.
 * @return an array of arrays that contain the original items
 * @param array contains the items of which all combinations are desired
 * @param depth is for internal use only
 */
function getCombinations( $array, $depth_at = 0 ) {

	if( $depth_at >= sizeof( $array )  ) {
		// stop condition
		$emptyArray = array();
		return array(array($emptyArray ));
	}
	/*$combinations = array();
	for( $i = $depth_at; $i < sizeof( $array ); $i++ ) {
		echo "i: $i <br />";
		$postfixes = getCombinations( $array, $i + 1 );
		echo "postfixes: ";
		var_dump( $postfixes );
		for( $j = 0; $j < sizeof( $postfixes ); $j++ ) {
			$combination = array();
			array_push( $combination, $array[$i] );
			for( $h = 0; $h < sizeof( $postfixes[$j] ); $h++ ) {
				//echo "i,j,h: $i,$j,$h <br />";
				array_push( $combination, $postfixes[$j][$h] );
			}
			array_push( $combinations, $combination );
		}
	}*/

	$combinations = array();
	//for( $i = $depth_at; $i < sizeof( $array ); $i++ ) {
		// get subtrees
		$postfixes = getCombinations( $array, $depth_at + 1 );
		//echo "L:".__LINE__." postfixes: ";
		//var_dump( $postfixes );


		// with self
		for( $k = 0; $k < sizeof( $postfixes ); $k++ ) {
			$combination = array();
			array_push( $combination, $array[$depth_at] );
			for( $j = 0; $j < sizeof( $postfixes[$k] ); $j++ ) {
				//print "L:".__LINE__." k, j : $k, $j \n";
				array_push( $combination, $postfixes[$k][$j] );
			}
			array_push( $combinations, $combination );
			//echo "L:".__LINE__." depth: $depth_at, combination: ";
			//var_dump( $combination );
		}
		//echo "L:".__LINE__." postfixes: ";
		//var_dump( $postfixes );

		// without self
		for( $k = 0; $k < sizeof( $postfixes ); $k++ ) {
			//$combination = array();
			//for( $j = 0; $j < sizeof( $postfixes[$k] ); $j++ ) {
			//	array_push( $combination, $postfixes[$k][$j] );
			//}
			//array_push( $combinations, $combination );
			array_push( $combinations, $postfixes[$k] );
			//echo "L:".__LINE__." depth: $depth_at, combination: ";
			//var_dump( $combination );
			//var_dump( $postfixes[$k] );
		}

		//// add self
		//array_push( $combinations, $array[$depth_at] );
	//}
	//echo "L:".__LINE__." depth: $depth_at, combinations: ";
	//var_dump( $combination );
	//var_dump( $combinations );



	return( $combinations );
}


function findReferencesToColumn( $tableName, $columnName ) {
	$ret = array(); // array containing referncing columns
	foreach( con::$tables as $refTablename=>$refColumns ) {
		foreach( $refColumns as $k=>$refColumn ) {
			if( array_key_exists( 2, $refColumn )
				&& $refColumn[2]['referenced_column_name'] != null
				&& $refColumn[2]['referenced_table_name'] != null
				&& strtolower($refColumn[2]['referenced_column_name'])
					== strtolower($columnName)
				&& strtolower($refColumn[2]['referenced_table_name'])
					== strtolower($tableName) ) {
				array_push( $ret, $refColumn[2] );
			}
		}
	}
	return( $ret );
}


?>
